# 版本: 1.0.0
# 作者: 陈振玺
# 功能: HTTP服务器核心模块

import os
import threading
import uvicorn
from fastapi import FastAPI, HTTPException
from fastapi.staticfiles import StaticFiles
from fastapi.responses import FileResponse
from pathlib import Path
import logging


class HTTPServer:
    """
    HTTP服务器类
    
    提供静态文件服务，监听指定IP地址和端口
    
    版本: 1.0.0
    作者: 陈振玺
    """
    
    def __init__(self, host: str = "192.168.10.98", port: int = 2121, serve_dir: str = None):
        """
        初始化HTTP服务器
        
        Args:
            host (str): 服务器IP地址，默认192.168.10.98
            port (int): 服务器端口，默认2121
            serve_dir (str): 服务目录路径，默认为当前目录下的www文件夹
        """
        self.host = host
        self.port = port
        self.serve_dir = serve_dir or os.path.join(os.getcwd(), "www")
        self.app = FastAPI(title="HTTP Server", version="1.0.0")
        self.server_thread = None
        self.is_running = False
        
        # 确保服务目录存在
        os.makedirs(self.serve_dir, exist_ok=True)
        
        # 配置日志
        logging.basicConfig(level=logging.INFO)
        self.logger = logging.getLogger(__name__)
        
        # 设置路由
        self._setup_routes()
    
    def _setup_routes(self):
        """
        设置路由
        """
        # 挂载静态文件目录
        self.app.mount("/static", StaticFiles(directory=self.serve_dir), name="static")
        
        @self.app.get("/")
        async def root():
            """根路径处理"""
            return {"message": "HTTP Server is running", "version": "1.0.0", "author": "陈振玺"}
        
        @self.app.get("/files/{file_path:path}")
        async def serve_file(file_path: str):
            """提供文件服务"""
            full_path = os.path.join(self.serve_dir, file_path)
            
            if not os.path.exists(full_path):
                raise HTTPException(status_code=404, detail="File not found")
            
            if os.path.isfile(full_path):
                return FileResponse(full_path)
            else:
                raise HTTPException(status_code=400, detail="Path is not a file")
        
        @self.app.get("/list/{dir_path:path}")
        async def list_directory(dir_path: str = ""):
            """列出目录内容"""
            full_path = os.path.join(self.serve_dir, dir_path)
            
            if not os.path.exists(full_path):
                raise HTTPException(status_code=404, detail="Directory not found")
            
            if not os.path.isdir(full_path):
                raise HTTPException(status_code=400, detail="Path is not a directory")
            
            try:
                items = []
                for item in os.listdir(full_path):
                    item_path = os.path.join(full_path, item)
                    is_dir = os.path.isdir(item_path)
                    items.append({
                        "name": item,
                        "type": "directory" if is_dir else "file",
                        "path": os.path.join(dir_path, item).replace("\\", "/")
                    })
                
                return {
                    "directory": dir_path,
                    "items": items
                }
            except PermissionError:
                raise HTTPException(status_code=403, detail="Permission denied")
    
    def start(self, background: bool = False):
        """
        启动服务器
        
        Args:
            background (bool): 是否在后台运行
        """
        if self.is_running:
            self.logger.warning("服务器已经在运行中")
            return
        
        self.logger.info(f"启动HTTP服务器: http://{self.host}:{self.port}")
        self.logger.info(f"服务目录: {self.serve_dir}")
        
        if background:
            self.server_thread = threading.Thread(
                target=self._run_server,
                daemon=True
            )
            self.server_thread.start()
        else:
            self._run_server()
    
    def _run_server(self):
        """
        运行服务器
        """
        try:
            self.is_running = True
            uvicorn.run(
                self.app,
                host=self.host,
                port=self.port,
                log_level="info"
            )
        except Exception as e:
            self.logger.error(f"服务器启动失败: {e}")
        finally:
            self.is_running = False
    
    def stop(self):
        """
        停止服务器
        """
        if not self.is_running:
            self.logger.warning("服务器未在运行")
            return
        
        self.logger.info("正在停止服务器...")
        self.is_running = False
        
        if self.server_thread and self.server_thread.is_alive():
            self.server_thread.join(timeout=5)
    
    def get_server_url(self):
        """
        获取服务器URL
        
        Returns:
            str: 服务器URL
        """
        return f"http://{self.host}:{self.port}"
    
    def get_file_url(self, file_path: str):
        """
        获取文件访问URL
        
        Args:
            file_path (str): 相对于服务目录的文件路径
        
        Returns:
            str: 文件访问URL
        """
        # 确保路径使用正斜杠
        file_path = file_path.replace("\\", "/")
        if file_path.startswith("/"):
            file_path = file_path[1:]
        
        return f"{self.get_server_url()}/files/{file_path}"